﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.Objects.DataClasses;
using System.Data.Common;
using System.Data;
using System.Data.SqlClient;
using Models;

namespace DataAccess
{
  public class Repository
  {
    public ClickReadDataBaseEntities db = new ClickReadDataBaseEntities();
    private string connectionString { get; set; }

    public Repository()
    {
      this.connectionString = @"Data Source=.\sqlexpress;Initial Catalog=ClickRead;Integrated Security=True";
    }

    public Repository(string connection)
    {
      this.connectionString = connection;
    }

    #region Basics
    //
    // Persistence 

    public void Save()
    {
      db.SaveChanges();
    }

    public void Insert<T>(T item) where T : EntityObject
    {
      db.CreateObjectSet<T>().AddObject(item);
    }

    public void Delete<T>(T entity) where T : EntityObject
    {
      db.CreateObjectSet<T>().DeleteObject(entity);
    }

    public void Delete<T>(System.Linq.Expressions.Expression<Func<T, bool>> whereclause) where T : EntityObject
    {
      db.CreateObjectSet<T>().DeleteObject(Get<T>(whereclause));
    }

    public T Get<T>(System.Linq.Expressions.Expression<Func<T, bool>> whereclause) where T : EntityObject
    {
      return db.CreateObjectSet<T>().Where(whereclause).SingleOrDefault();
    }

    public IEnumerable<T> Where<T>(System.Linq.Expressions.Expression<Func<T, bool>> whereclause) where T : EntityObject
    {
      return db.CreateObjectSet<T>().Where(whereclause);
    }

    public int Count<T>(System.Linq.Expressions.Expression<Func<T, bool>> where) where T : EntityObject
    {
      return db.CreateObjectSet<T>().Where(where).Count();
    }

    public IEnumerable<T> ExecuteRawQuery<T>(string sql) where T : EntityObject
    {
      return db.ExecuteStoreQuery<T>(sql);
    }
    #endregion

    #region Pages
    public SinglePage GetPage(int bookID, int pageID)
    {
      var page = this.Get<Page>(p => p.BookID == bookID && p.PageID == pageID);
      return new SinglePage()
      {
        Image = page.Image,
        pageID = page.PageID,
        Spots = this
         .Where<Spot>(s => s.BookID == page.BookID && s.PageID == page.PageID && !string.IsNullOrEmpty(s.Coords) && !string.IsNullOrEmpty(s.Shape))
         .Select(s => new HotArea()
         {
           HotAreaID = string.Format("{0}_{1}_{2}", s.BookID.ToString(), s.PageID.ToString(), s.SpotID.ToString()),
           Coords = s.Coords,
           Shape = s.Shape,
           Sound = s.Sound,
           Alt = s.Alt,
           Words = s.Words,
           Symbol = s.Symbols,
           Meaning = s.Meaning,
           TypeID = s.TypeID
         }).ToList()
      };
    }
    #endregion

    #region Books
    public List<SingleBook> GetBooks()
    {
      return this.db.Books.Select(b =>
        new SingleBook()
        {
          BookID = b.BookID,
          Name = b.Name,
          Album=b.Album,
          Image=b.Image,
          Press=b.Press,
          PageCount=b.PageCount
        }).ToList();
    }
    #endregion
  }
}
